<?php

	class ArchivePressOptions {
		// constants
		const YES							= "yes";
		const NO							= "no";
		
		const COMMENTS_CLOSED				= "closed";
		const COMMENTS_OPEN					= "open";
		
		const POST_PUBLISH					= "publish";
		const POST_DRAFF					= "draft";
		const POST_PENDING					= "pending";
		
		const CRON_WPCRON					= "wpcron";
		const CRON_WEBCRON					= "webcron";
		const CRON_UNIXCRON					= "unixcron";
		
		const PLUGIN_VERSION				= "1.0.0";
		const PLUGIN_FEEDSTABLE_NAME		= "feeds";
		const PLUGIN_FEEDLINKSTABLE_NAME	= "feed_links";
		const PLUGIN_FEEDMETATABLE_NAME		= "feed_meta";
		const PLUGIN_FEEDOPTIONSTABLE_NAME	= "feed_options";
		const PLUGIN_FEEDUSERSTABLE_NAME	= "feed_users";
		const PLUGIN_LOGTABLE_NAME			= "logs";
		
		const FEED_PROTOCOL_RSS		= "rss";
			const RSS_VERSION_0_90	= "0.90";
			const RSS_VERSION_0_91	= "0.91";
			const RSS_VERSION_1_0	= "1.0";
			const RSS_VERSION_2_0	= "2.0";
			
		const FEED_PROTOCOL_ATOM	= "atom";
			const ATOM_VERSION_0_3	= "0.3";
			const ATOM_VERSION_1_0	= "1.0";
			
		const FETCH_INTERVAL_DAILY	= 86400;
		const FETCH_INTERVAL_BID	= 43200;
		const FETCH_INTERVAL_TID	= 28800;
		const FETCH_INTERVAL_FOURTAD= 21600;
		const FETCH_INTERVAL_HOURLY	= 3600;
		
		const FEED_NAME				= "name";
		const ADMIN_USER			= "user";
		const USE_DEF_CAT			= "useDefaultCategory";
		
		const DEFAULT_HTML_TAGS		= "<div><p><h1><h2><h3><h4><h5><h6><ul><ol><li><dl><dt><dd><address><hr><pre><blockquote><center><ins><del><a><span><bdo><br><em><strong><dfn><code><samp><kbd><bar><cite><abbr><acronym><q><sub><sup><tt><i><b><big><small><u><s><strike><basefont><font><object><param><img><table><caption><colgroup><col><thead><tfoot><tbody><tr><th><td><embed>";
		
		const DEFAULT_CONTRIBUTORS	= "Contributors";
				
		// default options
		// PLUGIN OPTIONS
		public $pluginVersion		= self::PLUGIN_VERSION;
		public $feedsTableName		= self::PLUGIN_FEEDSTABLE_NAME;
		public $feedLinksTableName	= self::PLUGIN_FEEDLINKSTABLE_NAME;
		public $feedMetaTableName	= self::PLUGIN_FEEDMETATABLE_NAME;
		public $feedOptionsTableName= self::PLUGIN_FEEDOPTIONSTABLE_NAME;
		public $feedUsersTableName	= self::PLUGIN_FEEDUSERSTABLE_NAME;
		public $logTableName		= self::PLUGIN_LOGTABLE_NAME;
		public $embedMedia			= self::YES;
		public $cronType			= self::CRON_WPCRON;
		// FEED OPTIONS
		public $defFeedProtocol		= self::FEED_PROTOCOL_RSS;
		public $defRssVersion		= self::RSS_VERSION_2_0;
		public $defAtomVersion		= self::ATOM_VERSION_1_0;
		public $defFeedFetchInt		= self::FETCH_INTERVAL_DAILY;
		public $justAddedIsActive	= self::YES;
		public $showWhatWillDo		= self::YES;
		public $followPermaLink		= self::NO;
		public $keepPostAuth		= self::YES;
		public $defAuthor			= self::FEED_NAME;
		public $keepPostCategories	= self::YES;
		public $defCategory			= self::USE_DEF_CAT;
		public $tryAutoTag			= self::NO;
		public $YahooKey			= NULL;
		public $useCategoriesAsTags	= self::YES;
		public $defPostStatus		= self::POST_PUBLISH;
		public $defCommentsStatus	= self::COMMENTS_CLOSED;
		public $postFetchComments	= self::YES;
		public $tryTypePadStandard	= self::NO;
		public $areCommentsApproved	= self::YES;
		public $htmlAllowedTags		= self::DEFAULT_HTML_TAGS;
		public $saveContributors	= self::YES;
		public $defContributorLink	= self::DEFAULT_CONTRIBUTORS;	
		public $tryToFindExcerpt	= self::YES;
		// LOG OPTIONS
		public $defLogStatus		= ArchivePressLog::LOG_OFF;
		public $defLogLevel			= ArchivePressLog::LOG_BASIC;
		// PRIVATE OPTIONS
		public $pluginDelIsAllowed	= self::NO;
		public $tryTypePadAttempts	= 10;
	}

	class ArchivePress {
		// constants
		
		
		// properties
		public $options;				// options
		public $lastAdded;				// last added feed
		
		public $lastFeedCheckedProt;	// feed protocol (the last checked)
		public $lastFeedCheckedVers;	// feed protocol version (the last checked)
		public $lastFeedCheckedUrl;		// last url tested
		public $lastFeedCheckedLink;	// last blog link
		
		private $FeedReader = NULL;		// feed reader class
		private $wpdb;					// global wp db class
		private $Log;					// logging class
		
		// table names
		private $feedTable;
		private $feedOptions;
		private $feedMeta;
		private $feedLinks;
		private $feedUsers;
		
		
		// methods
		function __construct(ArchivePressOptions $options = NULL){
			// Init Options
			if(isset($options)){
				$this->options = $options;
			}else{ // uses default options
				$this->options = new ArchivePressOptions();
			}
			
			// set global db connection (and class)
			global $wpdb;
			$this->wpdb = $wpdb;
			
			// Internationalization
			$this->options->defContributorLink = __($this->options->defContributorLink,ARCHIVEPRESS);
			
			// bring user saved options inside the class (override default settings with the user's one)
			$this->refreshClassOptions();
			
			// db table names
			$this->feedTable	= $this->wpdb->prefix . WP_ARCHIVEPRESS_PREFIX . $this->options->feedsTableName;
			$this->feedLinks	= $this->wpdb->prefix . WP_ARCHIVEPRESS_PREFIX . $this->options->feedLinksTableName;
			$this->feedOptions	= $this->wpdb->prefix . WP_ARCHIVEPRESS_PREFIX . $this->options->feedOptionsTableName;
			$this->feedMeta		= $this->wpdb->prefix . WP_ARCHIVEPRESS_PREFIX . $this->options->feedMetaTableName;	
			$this->feedUsers	= $this->wpdb->prefix . WP_ARCHIVEPRESS_PREFIX . $this->options->feedUsersTableName;
			$this->logTable		= $this->wpdb->prefix . WP_ARCHIVEPRESS_PREFIX . $this->options->logTableName;
			
			// log class
			global $ArchivePressLog;
			$ArchivePressLog	= new ArchivePressLog($this->logTable,$this->options->defLogStatus,$this->options->defLogLevel);
			$this->Log			= $ArchivePressLog;
			
			// feed reader class
			$this->FeedReader = new FeedReader();
		}
		
		// check if a link provided is already a feed
		function isFeed($url,$content=NULL){
			$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("START: check url '%s'",ARCHIVEPRESS), $url));
			
			$lastFeedCheckedUrl = $url;
			try {
				if( $this->FeedReader->isFeed($url,$content) == false ){
					$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("END: the url '%s',  is not a feed url.",ARCHIVEPRESS), $url));
					return false;
				} else {
					if($this->FeedReader->isRss){
						$this->lastFeedCheckedProt = ArchivePressOptions::FEED_PROTOCOL_RSS;
						$this->lastFeedCheckedVers = $this->FeedReader->feedVersion;
					} else{
						$this->lastFeedCheckedProt = ArchivePressOptions::FEED_PROTOCOL_ATOM;
						$this->lastFeedCheckedVers = ArchivePressOptions::ATOM_VERSION_1_0;
					}
					$this->lastFeedCheckedUrl  = $url;
					$this->lastFeedCheckedLink = $this->FeedReader->blogUrl;
					$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("END: the url '%s',  is a feed url.",ARCHIVEPRESS), $url));
					return true;
				}
			} catch (Exception $e) {
				// page not found or other curl errors
				$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("%s: page not found!=",ARCHIVEPRESS), $url));
				throw new Exception(__('Page not found',ARCHIVEPRESS));
			}
		}
		
		// add the last feed link checked
		function addLastCheckedFeed($name,$checkDatabaseBefore = true,$isComment="no"){
			$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("START: add feed '%s'",ARCHIVEPRESS), $name));
			
			// if required check if the feed is already inside the db
			if($checkDatabaseBefore){
				$myrows = $this->wpdb->get_row( "SELECT id FROM ".$this->feedLinks." WHERE url = '".$this->wpdb->escape($this->lastFeedCheckedUrl)."' ", OBJECT );
				// if already added
				if(isset($myrows)) {
					throw new Exception(__('Feed already exists',ARCHIVEPRESS));
					$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("Feed '%s' already exists.",ARCHIVEPRESS), $name));
				}
			}
			// check before if the name is UNIQUE
			$myrows = $this->wpdb->get_row( "SELECT id FROM ".$this->feedTable." WHERE name = '".$this->wpdb->escape($name)."' ", OBJECT);
			// if exists already
			if(isset($myrows)) {
				throw new Exception(__('Feed name already exists',ARCHIVEPRESS));
				$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("Feed name '%s' already exists.",ARCHIVEPRESS), $name));
			}
			
			// add it into the database
			// feed
			$this->wpdb->query("INSERT INTO ".$this->feedTable." 
								(id,name,url,protocol,version,feed_date,last_update,is_comment,active,last_fetched) 
								VALUES ('','".$this->wpdb->escape($name)."','".$this->wpdb->escape($this->lastFeedCheckedUrl)."','".$this->wpdb->escape($this->lastFeedCheckedProt)."','".$this->wpdb->escape($this->lastFeedCheckedVers)."',FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s'))."),FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s'))."),'".$isComment."','".$this->wpdb->escape($this->options->justAddedIsActive)."',NULL) ");
			$myrows = $this->wpdb->get_row( "SELECT id FROM ".$this->feedTable." WHERE url = '".$this->wpdb->escape($this->lastFeedCheckedUrl)."' ", ARRAY_A);
			// options
			// fetch interval
			$this->wpdb->query("INSERT INTO ".$this->feedOptions." 
								(id,feed_id,name,value) 
								VALUES ('','".$myrows['id']."','interval','".$this->wpdb->escape($this->options->defFeedFetchInt)."')");
			// fetch also comments
			$this->wpdb->query("INSERT INTO ".$this->feedOptions." 
								(id,feed_id,name,value) 
								VALUES ('','".$myrows['id']."','comments','".$this->wpdb->escape($this->options->postFetchComments)."')");
			// is new (to allow feed upload)
			$this->wpdb->query("INSERT INTO ".$this->feedOptions." 
									(id,feed_id,name,value) 
									VALUES ('','".$myrows['id']."','is_new','yes')");
			
			// meta
			// Added when feed fetched
		
			// links
			$this->wpdb->query("INSERT INTO ".$this->feedLinks." 
								(id,feed_id,url,is_the_one_in_use) 
								VALUES ('','".$myrows['id']."','".$this->wpdb->escape($this->lastFeedCheckedUrl)."','yes')");
			
			
			// if required save also as Contributor
			if($this->options->saveContributors == ArchivePressOptions::YES){
				require_once(ABSPATH . "/wp-admin/includes/bookmark.php");
				// get contributor link category
				$category = $this->options->defContributorLink;
				$term = get_term_by( 'name', sanitize_title($category), 'link_category',ARRAY_A );
				if($term === false){
					$term = wp_insert_term( $category, 'link_category' );
				}
				$link_id = wp_insert_link(array("link_name" => $name, "link_url" => $this->lastFeedCheckedLink ));
				// HACK to update the link category properly
				$oldDefCat = get_option("default_link_category");
				update_option("default_link_category",(int)$term["term_id"]);
				wp_set_link_cats( $link_id );
				update_option("default_link_category",$oldDefCat);
				// END: HACK to update the link category properly
			}
			
			$this->lastAdded = $myrows['id'];
			
			$this->Log->logIt(ArchivePressLog::LOG_BASIC,sprintf(__("Feed '%s' successfully added.",ARCHIVEPRESS), $name));
			return true;
		}
		// add a feed starting from many links (they are the ones found with the autodiscovery procedure)
		function addFeed(array $feeds,$url,$name){
			$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("START: add feed from url: '%s'",ARCHIVEPRESS), $url));
			
			$firstFeed = array();
			$otherFeeds = array();
			// for each link I get the first feed
			// then I compare all the first feeds to see if
			// they are the same in different protols (like rss and atom)
			// or if they are different feeds (maybe posts and comments)
			// if DIFFERENT PROTOCOLS> add the feed with the default protocol
			// else ASK to the user
			for($i=0;$i<count($feeds);$i++){
				try {
					$first = array();
					$first = $this->FeedReader->getFirstFeed($feeds[$i]);
					
					if($i == 0){
						// I add the first
						$first['url'] = $feeds[$i];
						array_push($firstFeed,$first);
					} else if( ($first['title'] != $firstFeed[count($firstFeed)-1]['title']) && ($first['link'] != $firstFeed[count($firstFeed)-1]['link']) ){
						// I check the others
						$first['url'] = $feeds[$i];
						array_push($firstFeed,$first);
					} else if($firstFeed[count($firstFeed)-1]['protocol'] != $this->options->defFeedProtocol){
						// if the new feed is the same I have to keep the one 
						// with the default protocol
						$item = array_pop($firstFeed);
						array_push($otherFeeds,$item);
						$first['url'] = $feeds[$i];
						array_push($firstFeed,$first);
					} else {
						$first['url'] = $feeds[$i];
						array_push($otherFeeds,$first);
					}
				} catch (Exception $e) {
					// page not found or other curl errors
					$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("%s: page not found!=",ARCHIVEPRESS), $first['url']));
				}
			}
			$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("%d feed links found.",ARCHIVEPRESS), count($firstFeed)));
			if(count($firstFeed)==1){
				// add the feed
				// check before if the name is UNIQUE
				$myrows = $this->wpdb->get_row( "SELECT id FROM ".$this->feedTable." WHERE name = '".$this->wpdb->escape($name)."' ", OBJECT);
				// if exists already
				if(isset($myrows)) {
					$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("Feed name '%s' already exists.",ARCHIVEPRESS), $name));
					throw new Exception(__('Feed name already exists',ARCHIVEPRESS));
					return false;
				}
					
				// 1. the selected one
				$this->wpdb->query("INSERT INTO ".$this->feedTable." 
									(id,name,url,protocol,version,feed_date,last_update,is_comment,active,last_fetched) 
									VALUES ('','".$this->wpdb->escape($name)."','".$this->wpdb->escape($url)."','".$this->wpdb->escape($firstFeed[0]["protocol"])."','".$this->wpdb->escape($firstFeed[0]["version"])."',FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s'))."),FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s'))."),'no','".$this->wpdb->escape($this->options->justAddedIsActive)."',NULL) ");
				$myrows = $this->wpdb->get_row( "SELECT id FROM ".$this->feedTable." WHERE url = '".$this->wpdb->escape($url)."' ", ARRAY_A);
				// options
				// fetch interval
				$this->wpdb->query("INSERT INTO ".$this->feedOptions." 
									(id,feed_id,name,value) 
									VALUES ('','".$myrows['id']."','interval','".$this->wpdb->escape($this->options->defFeedFetchInt)."')");
				// fetch also comments
				$this->wpdb->query("INSERT INTO ".$this->feedOptions." 
									(id,feed_id,name,value) 
									VALUES ('','".$myrows['id']."','comments','".$this->wpdb->escape($this->options->postFetchComments)."')");
				// is new (to allow feed upload)
				$this->wpdb->query("INSERT INTO ".$this->feedOptions." 
									(id,feed_id,name,value) 
									VALUES ('','".$myrows['id']."','is_new','yes')");
				
				// meta
				// Added when feed fetched
			
				// links					
				$this->wpdb->query("INSERT INTO ".$this->feedLinks." 
									(id,feed_id,url,is_the_one_in_use) 
									VALUES ('','".$myrows['id']."','".$this->wpdb->escape($firstFeed[0]["url"])."','yes')");
				// 2. other links
				for($i=0;$i<count($otherFeeds);$i++){
					$this->wpdb->query("INSERT INTO ".$this->feedLinks." 
										(id,feed_id,url,is_the_one_in_use) 
										VALUES ('','".$myrows['id']."','".$this->wpdb->escape($otherFeeds[$i]["url"])."','no')");
				}
				
				// if required save also as Contributor
				if($this->options->saveContributors == ArchivePressOptions::YES){
					require_once(ABSPATH . "/wp-admin/includes/bookmark.php");
					// get contributor link category
					$category = $this->options->defContributorLink;
					$term = get_term_by( 'name', sanitize_title($category), 'link_category',ARRAY_A );
					if($term === false){
						$term = wp_insert_term( $category, 'link_category' );
					}
					$link_id = wp_insert_link(array("link_name" => $name, "link_url" => $url ));
					// HACK to update the link category properly
					$oldDefCat = get_option("default_link_category");
					update_option("default_link_category",(int)$term["term_id"]);
					wp_set_link_cats( $link_id );
					update_option("default_link_category",$oldDefCat);
					// END: HACK to update the link category properly
				}
					
				
				$this->Log->logIt(ArchivePressLog::LOG_BASIC,sprintf(__("Feed '%s' successfully added.",ARCHIVEPRESS), $name));
				return true;
			}else {
				return $firstFeed;
			}
		}
		
		// Check if a feed was already previously added
		function isFeedNew(array $feeds){
			for($i=0;$i<count($feeds);$i++){
				// check if it is already added [database]
				$myrows = $this->wpdb->get_row( "SELECT id FROM ".$this->feedLinks." WHERE url = '".$this->wpdb->escape($feeds[$i])."' ", OBJECT );
				// if already added
				if(isset($myrows))
					return false;
			}
			return true;
		}

		// fetch feed procedure
		public function fetchFeed(array $feed) {
			$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("START: fetch feed '%s' (%s)",ARCHIVEPRESS), $feed["name"], $feed["url"]));
			
			require_once(ABSPATH . WPINC . '/registration.php');
			
			// update feed status: it is not new anymore
			// is new (to allow feed upload)
			// it's less expensive to ask before: a selection is faster than an update!
			$value= $this->wpdb->get_var($this->wpdb->prepare("SELECT value FROM ".$this->feedOptions." WHERE name = %s AND feed_id = %d", "is_new",(int)$feed['id']));
			if($value == "yes"){
				$this->wpdb->query("UPDATE ".$this->feedOptions." 
									SET value = 'no' 
									WHERE name = 'is_new' AND feed_id = '".$feed['id']."'");
			}
			
			$posts = array();
			
			try {
				if(array_key_exists("file",$feed)){
					$file = $feed["file"];
				} else {
					$file = NULL;
				}
				$posts = $this->FeedReader->fetch($feed["url"],$feed["protocol"],$feed["last_fetched"],NULL,$file);
				if(count($posts) > 0){
					// update last fetched and last update time
					$this->wpdb->query("UPDATE ".$this->feedTable." SET last_fetched='".$this->wpdb->escape($posts[0]["lastFetched"])."', last_update=FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s')).") WHERE id='".(int)$feed["id"]."'");

					// add metadata
					// 1. look for metadata
					$feed_id = (int)$feed["id"];
					$value = $this->wpdb->get_var($this->wpdb->prepare("SELECT value FROM ".$this->feedMeta." WHERE feed_id = %d", $feed_id));
					if(!$value){
						// not found --> add
						$this->wpdb->query("INSERT INTO ".$this->feedMeta." 
											(id,feed_id,value,meta_date) 
											VALUES ('','".$feed_id."','".$this->wpdb->escape($posts[0]["metadata"])."',FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s'))."))");
					} else if (unserialize($posts[0]["metadata"]) !== unserialize($value)) {
						// 2. metadata found: if not changed --> do nothing else add (this is a metadata log)
						$this->wpdb->query("INSERT INTO ".$this->feedMeta." 
											(id,feed_id,value,meta_date) 
											VALUES ('','".$feed_id."','".$this->wpdb->escape($posts[0]["metadata"])."',FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s'))."))");
					}
					
					
					// typepad comments option
					if(($this->options->tryTypePadStandard == ArchivePressOptions::YES) && ($this->options->postFetchComments == ArchivePressOptions::YES) ){
						$isTypePad = $this->wpdb->get_var($this->wpdb->prepare("SELECT value FROM ".$this->feedOptions." WHERE feed_id = %d AND name = %s", $feed_id,"isTypePad"));
						if($isTypePad){
							if($isTypePad == "yes"){
								$isTypePad = true;	
							}else {
								$isTypePad = false;
								$typePadCounter = $this->wpdb->get_var($this->wpdb->prepare("SELECT value FROM ".$this->feedOptions." WHERE feed_id = %d AND name = %s", $feed_id,"TypePadCounter"));
							}
						} else {
							$isTypePad = false;
							$typePadCounter = 0;
							$this->wpdb->query("INSERT INTO ".$this->feedOptions." 
									(id,feed_id,name,value) 
									VALUES ('','".$feed_id."','TypePadCounter','".$this->wpdb->escape($typePadCounter)."')");
							$this->wpdb->query("INSERT INTO ".$this->feedOptions." 
									(id,feed_id,name,value) 
									VALUES ('','".$feed_id."','isTypePad','no')");
						}
						
					}
					
					// insert posts
					foreach($posts as $post) {
						// AUTHOR
						$user_id = "";
						if(($this->options->keepPostAuth == ArchivePressOptions::YES) && ($post["author"] != "") && (strtolower($post["author"]) != "admin") ) {
							$post["author"] = sanitize_user($post["author"],true);
						} else if(($this->options->keepPostAuth == ArchivePressOptions::YES) && (strtolower($post["author"]) != "admin") ) {
							// DON'T USE ADMIN
							$post["author"] = sanitize_user($post["category"],true);
						} else if(($this->options->keepPostAuth == ArchivePressOptions::NO) || ($post["author"] != "")){
							// 2 options: use the category or use the admin author
							if($this->options->defAuthor == ArchivePressOptions::FEED_NAME) {
								$post["author"] = sanitize_user($post["category"],true);
							} else if($this->options->defAuthor == ArchivePressOptions::ADMIN_USER) {
								$post["author"] = "admin";
							} else {
								$user_id = (int)$this->options->defAuthor;
							}
						}
						if($user_id == "") {
							$user_id = username_exists( $post["author"].sanitize_user("@".str_replace(" ","",substr($post["category"],0,6))) );
						}
						$isNewUser = false;
						if ( !isset($user_id)) {
							$random_password = wp_generate_password( 12, false );
							$user_email = $this->getNewMail();
							if(array_key_exists("email",$post)) {
								$user_email = $post["email"];
							}
							// as username I use the name plus an original blog identifier
							// to prevent duplicate
							$userName = $post["author"].sanitize_user("@".str_replace(" ","",substr($post["category"],0,6)));
							$user_id = wp_create_user( $userName, $random_password, $user_email );
							// modify now the Public Name, using the original user name
							wp_update_user(array("ID" => $user_id,"user_url" => $post["author_url"],"display_name" => $post["author"]) );
							$isNewUser = true;
						}
						// CATEGORIES
						if($this->options->keepPostCategories == ArchivePressOptions::YES) {
							// uses the feed title as post category
							$category_id = get_cat_id($post["category"]);
							if ( !$category_id ) {
								require_once(ABSPATH . "/wp-admin/includes/taxonomy.php");
								$category_id = wp_create_category($post["category"], 0);
								wp_update_term( $category_id, 'category', array("description"=>$post["subtitle"]) );
							}
						} else if ($this->options->defCategory == ArchivePressOptions::USE_DEF_CAT) {
							// uses the default category
							$category_id = get_option('default_category');
						} else {
							// uses another category
							$category_id = (int)$this->options->defCategory;
						}
						$category = array();
						array_push($category,$category_id);
						// TAGS
						if(count($post["tags"])>0){
							$tags = implode(", ",$post["tags"]);
						}else{
							$tags = "";
						}
						// DATES
						$dates = array();
						$dates = $this->getDates($post["pubDate"],$feed["protocol"]);
						// UPDATE DATES
						if(array_key_exists("upDate",$post)){
							$updates = array();
							$updates = $this->getDates($post["upDate"],$feed["protocol"]);						
						}
						
						// update content:
						// 1. fix relative links
						// 2. update links in case they are pointing to already added posts
						$internalLinks = $post["internalLinks"];
						for($i=0;$i<count($internalLinks);$i++){
							$link_to_check = $internalLinks[$i];
							// check if the link is pointing on a already added post
							$post_id = $this->wpdb->get_var($this->wpdb->prepare("SELECT post_id FROM ".$this->wpdb->postmeta." WHERE meta_value = %s", $link_to_check));
							if($post_id){
								// update link
								$post["content"] = str_replace($link_to_check,get_permalink( $post_id ),$post["content"]);
							}
						}
						
						// CHECK IF IS NEW OR IF IS AN UPDATE
						$meta_value = $post["link"];
						$post_id = $this->wpdb->get_var($this->wpdb->prepare("SELECT post_id FROM ".$this->wpdb->postmeta." WHERE meta_value = %s", $meta_value));
						// if not already added
						if(!$post_id) {				
							// ADD POST
							$newPost = array();
							$newPost["post_status"]		= $this->options->defPostStatus; 
							$newPost["comment_status"] 	= $this->options->defCommentsStatus;
							$newPost["post_author"] 	= $user_id;
							$newPost["post_category"] 	= $category;
							$newPost["post_content"] 	= $post["content"];
							$newPost["post_excerpt"]	= $post["excerpt"];
							$newPost["post_date"] 		= $dates["date"];
							$newPost["post_date_gmt"] 	= $dates["gmt"];
							$newPost["post_name"] 		= sanitize_title($post["title"]);
							$newPost["post_title"] 		= $post["title"];
							$newPost["post_type"] 		= 'post';
							$newPost["tags_input"] 		= $tags;
							$post_id = wp_insert_post( $newPost );
							
							// ATTACHMENTS
							if(array_key_exists("media",$post)){
								require_once(ABSPATH . "/wp-admin/includes/image.php");
								foreach($post["media"] as $media) {
									if($media["type"] == "img"){
										$attach_id = wp_insert_attachment( $newPost, $media["path"], $post_id );
										$attach_data = wp_generate_attachment_metadata( $attach_id, $media["path"] );
										wp_update_attachment_metadata( $attach_id,  $attach_data );
										// original meta link
										add_post_meta($attach_id, WP_ARCHIVEPRESS_PREFIX . 'ori_media_link', $media["oldUrl"]);
										// original post id
										add_post_meta($attach_id, WP_ARCHIVEPRESS_PREFIX . 'attached_post_id', $post_id);
									}
								}
							}
							
		  
							// POST META DATA
							// is syndacated
							add_post_meta($post_id, WP_ARCHIVEPRESS_PREFIX . 'is_syndacated', 'yes');
							// original url
							add_post_meta($post_id, WP_ARCHIVEPRESS_PREFIX . 'original_url', $post["link"]);
							// fetching date
							add_post_meta($post_id, WP_ARCHIVEPRESS_PREFIX . 'fetch_date', date("Y-m-d H:i:s"));
							// feed id
							add_post_meta($post_id, WP_ARCHIVEPRESS_PREFIX . 'feed_id', $feed["id"]);
							// feed guid
							add_post_meta($post_id, WP_ARCHIVEPRESS_PREFIX . 'feed_guid', $post["lastFetched"]);
							
							// IF REQUIRED: ADD COMMENTS FEED
							if($this->options->postFetchComments == ArchivePressOptions::YES){
								// SPECIAL CASE: Blogger DOESN'T include the link inside
								// the post item, BUT inside the post page
								// TO DISCOVER it I have to
								// 1. get ALL the feed links from the original post page
								// 2. remove the ones are about thblog (I have them already inside the db)
								// 3. add the last feed link: it is the comments one!
								// PS: this is just for BLOGGER, in the other cases it won't work
								if($post["comments"] == ""){
									$feeds = array();
									try {
										$feeds = FeedAutoDiscovery::getFeedLinks($post["link"]);
										for($i=0;$i<count($feeds);$i++){
											$link_count = $this->wpdb->get_var("SELECT COUNT(*) FROM ".$this->feedLinks." WHERE url = '".$this->wpdb->escape($feeds[$i])."' ");
											if($link_count == 0){
												$post["comments"] = $feeds[$i];
												break;
											}
										}
									} catch (Exception $e) {
										$this->Log->logIt(ArchivePressLog::LOG_DEBUG,__($e->getMessage(),ARCHIVEPRESS));
									}
									
								}
								if($post["comments"] != ""){
									if($this->isFeed($post["comments"])){
										// DON'T add link as contributor
										$oldOption = $this->options->saveContributors;
										$this->options->saveContributors = ArchivePressOptions::NO;
										$this->addLastCheckedFeed(sprintf(__("Comments on '%s'",ARCHIVEPRESS), $newPost["post_title"]),true,"yes");
										$this->options->saveContributors = $oldOption;
										// comments feed link
										add_post_meta($post_id, WP_ARCHIVEPRESS_PREFIX . 'comments', $this->lastAdded);
									} 
								}else if($this->options->tryTypePadStandard == ArchivePressOptions::YES) { // if required
									// Try TypePad STANDARD BLOG procedure
									// this means if it has custom fields it won't work!
									if(!$isTypePad){
										// number of attempts not reached
										if($typePadCounter < $this->options->tryTypePadAttempts) {
											if($this->FeedReader->isTypePad($post["link"])){
												$this->wpdb->query("UPDATE ".$this->feedOptions." 
																	SET value = 'yes'
																	WHERE feed_id = '".$feed_id."'
																	AND name = 'isTypePad'");
												$this->lastFeedCheckedProt = "html";
												$this->lastFeedCheckedVers = "html";
												$this->lastFeedCheckedUrl  = $post["link"];
												$this->lastFeedCheckedLink = $post["link"];
												// DON'T add link as contributor
												$oldOption = $this->options->saveContributors;
												$this->options->saveContributors = ArchivePressOptions::NO;
												$this->addLastCheckedFeed(sprintf(__("Comments on '%s'",ARCHIVEPRESS), $newPost["post_title"]),true,"yes");
												$this->options->saveContributors = $oldOption;
												// comments feed link
												add_post_meta($post_id, WP_ARCHIVEPRESS_PREFIX . 'comments', $this->lastAdded);
												$isTypePad = true;
											} else {
												// update TypePad Option counter
												$typePadCounter++;
												$this->wpdb->query("UPDATE ".$this->feedOptions." 
																	SET value = '".$this->wpdb->escape($typePadCounter)."'
																	WHERE feed_id = '".$feed_id."'
																	AND name = 'TypePadCounter'");
											}
										}
									} else {
										$this->lastFeedCheckedProt = "html";
										$this->lastFeedCheckedVers = "html";
										$this->lastFeedCheckedUrl  = $post["link"];
										$this->lastFeedCheckedLink = $post["link"];
										// DON'T add link as contributor
										$oldOption = $this->options->saveContributors;
										$this->options->saveContributors = ArchivePressOptions::NO;
										$this->addLastCheckedFeed(sprintf(__("Comments on '%s'",ARCHIVEPRESS), $newPost["post_title"]),true,"yes");
										$this->options->saveContributors = $oldOption;
										// comments feed link
										add_post_meta($post_id, WP_ARCHIVEPRESS_PREFIX . 'comments', $this->lastAdded);
									}
								}
							}
								
						} else {
							// UPDATE POST PROCEDURE
							$newPost = array();
							$newPost['ID'] = $post_id;
							$newPost["post_status"]		= $this->options->defPostStatus; 
							$newPost["comment_status"] 	= $this->options->defCommentsStatus;
							$newPost["post_author"] 	= $user_id;
							$newPost["post_category"] 	= $category;
							$newPost["post_content"] 	= $post["content"];
							$newPost["post_excerpt"]	= $post["excerpt"];
							if(isset($updates)){
								$newPost["post_date"] 		= $updates["date"];
								$newPost["post_date_gmt"] 	= $updates["gmt"];
							}else {
								$newPost["post_date"] 		= $dates["date"];
								$newPost["post_date_gmt"] 	= $dates["gmt"];
							}
							$newPost["post_name"] 		= sanitize_title($post["title"]);
							$newPost["post_title"] 		= $post["title"];
							$newPost["post_type"] 		= 'post';
							$newPost["tags_input"] 		= $tags;
							wp_update_post( $newPost );
							
							// ATTACHMENTS: NOT WORKING HERE....
							/*
									if(array_key_exists("media",$post)){
										require_once(ABSPATH . "/wp-admin/includes/image.php");
										foreach($post["media"] as $media) {
											if($media["type"] == "img"){
												$attach_id = wp_insert_attachment( $newPost, $media["path"], $post_id );
												$attach_data = wp_generate_attachment_metadata( $attach_id, $media["path"] );
												wp_update_attachment_metadata( $attach_id,  $attach_data );
												// original meta link
												add_post_meta($attach_id, WP_ARCHIVEPRESS_PREFIX . 'ori_media_link', $media["oldUrl"]);
												// original post id
												add_post_meta($attach_id, WP_ARCHIVEPRESS_PREFIX . 'attached_post_id', $post_id);
											}
										}
									}
							*/
							
							// POST META
							update_post_meta($post_id, WP_ARCHIVEPRESS_PREFIX . 'fetch_date', date("Y-m-d H:i:s"));
							
						}
						
						// add archivepress user data
						if($isNewUser) {
							// NOW IN wp_usermeta
							/*
								$this->wpdb->query("INSERT INTO ".$this->feedUsers." 
													(id,feed_id,ori_username,add_post_id,add_date) 
													VALUES ('','".$feed["id"]."','".$post["originalAuthor"]."','".$post_id."',FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s'))."))");
							*/
							// USER META
							// feed_id
							update_usermeta( $user_id, WP_ARCHIVEPRESS_PREFIX . 'feed_id', $feed["id"] );
							// ori_username
							update_usermeta( $user_id, WP_ARCHIVEPRESS_PREFIX . 'ori_username', $post["originalAuthor"] );
							// add_post_id
							update_usermeta( $user_id, WP_ARCHIVEPRESS_PREFIX . 'add_post_id', $post_id );
						}
	
					}
				}else {
					// update last_update
					$this->wpdb->query("UPDATE ".$this->feedTable." SET last_update=FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s')).") WHERE id='".(int)$feed["id"]."'");
				}
				$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(_n("%d posts added","%d post added",count($posts),ARCHIVEPRESS), count($posts)));
				return count($posts);
			} catch (Exception $e){
				$this->Log->logIt(ArchivePressLog::LOG_BASIC,__($e->getMessage(),ARCHIVEPRESS));
			}
		}
		
		// fetch feed comments
		public function fetchFeedComments($feed_id = 0){
			// search feed URLs
			$time = microtime(true);
			$myrows = $this->wpdb->get_results( "SELECT feed.id, feed.name, feed.protocol, feed.last_fetched, links.url 
												FROM ".$this->feedTable." AS feed 
												LEFT JOIN ".$this->feedLinks." AS links ON feed.id = links.feed_id 
												WHERE feed.active='yes' AND links.is_the_one_in_use = 'yes'
												AND feed.is_comment='yes'
												AND feed.id IN 
												(SELECT meta_value FROM ".$this->wpdb->postmeta." WHERE meta_key = '".WP_ARCHIVEPRESS_PREFIX."comments' 
												AND post_id IN (SELECT post_id FROM ".$this->wpdb->postmeta." WHERE meta_key = '".WP_ARCHIVEPRESS_PREFIX."feed_id' AND meta_value = '".(int)$feed_id."'  ) )
			 									", ARRAY_A );
			if($myrows) {
				foreach($myrows as $row){
					
					$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(__("START: fetch feed '%s' (%s)",ARCHIVEPRESS), $row["name"], $row["url"]));
					
					$posts = array();
					
					try {
						if($row["protocol"] != "html"){
							$comments = $this->FeedReader->fetch($row["url"],$row["protocol"],$row["last_fetched"]);
						} else {
							$comments = $this->FeedReader->fetchTypePadComments($row["url"],$row["last_fetched"]);
						}
							
						if(count($comments) > 0){
							// update last fetched and last update time
							$this->wpdb->query("UPDATE ".$this->feedTable." SET last_fetched='".$this->wpdb->escape($comments[0]["lastFetched"])."', last_update=FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s')).") WHERE id='".(int)$row["id"]."'");
						
							$post_id = $this->wpdb->get_var("SELECT post_id FROM ".$this->wpdb->postmeta." WHERE meta_key = '".WP_ARCHIVEPRESS_PREFIX."comments' AND meta_value = '".(int)$row["id"]."'");
							foreach($comments as $comment) {
								$dates = array();
								$dates = $this->getDates($comment["pubDate"],$row["protocol"]);
								$email = "";
								if(array_key_exists("email",$comment)){
									$email = $comment["email"];
								}
								$commentdata = array(
												'comment_post_ID'		=> $post_id,
											    'comment_author'		=> $comment["author"],
											    'comment_author_email'	=> $email,
											    'comment_author_url'	=> 'http://',
											    'comment_content'		=> $comment["content"],
											    'comment_author_IP'		=> $_SERVER['REMOTE_ADDR'],
											    'comment_date'			=> $dates["date"],
											    'comment_date_gmt'		=> $dates["gmt"],
												'comment_type'			=> "",
											    'comment_approved'		=> 1
												);
								if($this->options->areCommentsApproved == ArchivePressOptions::YES){
									// insert AUTO APPROVED comment
									$comment_id = wp_insert_comment( $commentdata );
								} else {
									// the comment will follow the wp rules
									$comment_id = wp_new_comment ( $commentdata );
								}
								if($comment_id){
									// metadata
									$this->wpdb->query("INSERT INTO ".$this->wpdb->prefix."commentmeta 
														(meta_id,comment_id,meta_key,meta_value) 
														VALUES ('','".$comment_id."','".WP_ARCHIVEPRESS_PREFIX."feed_guid','".$comment["lastFetched"]."')");
									$this->wpdb->query("INSERT INTO ".$this->wpdb->prefix."commentmeta 
														(meta_id,comment_id,meta_key,meta_value) 
														VALUES ('','".$comment_id."','".WP_ARCHIVEPRESS_PREFIX."feed_id','".$row["id"]."')");
									$this->wpdb->query("INSERT INTO ".$this->wpdb->prefix."commentmeta 
														(meta_id,comment_id,meta_key,meta_value) 
														VALUES ('','".$comment_id."','".WP_ARCHIVEPRESS_PREFIX."fetch_date',FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s'))."))");
									$this->wpdb->query("INSERT INTO ".$this->wpdb->prefix."commentmeta 
														(meta_id,comment_id,meta_key,meta_value) 
														VALUES ('','".$comment_id."','".WP_ARCHIVEPRESS_PREFIX."original_url','".$comment["link"]."')");
								
								}
							}
							
							$this->Log->logIt(ArchivePressLog::LOG_DEBUG,sprintf(_n("%d posts added","%d post added",count($posts),ARCHIVEPRESS), count($posts)));
						}else {
							// update last_update
							$this->wpdb->query("UPDATE ".$this->feedTable." SET last_update=FROM_UNIXTIME(".strtotime(date('Y-m-d H:i:s')).") WHERE id='".(int)$row["id"]."'");
						}
						
					} catch (Exception $e){
						$this->Log->logIt(ArchivePressLog::LOG_BASIC,__($e->getMessage(),ARCHIVEPRESS));
					}
				}
			}
		}
		
		// get feed
		public function getFeed($id){
			
		}
		
		// get all the feed
		public function getFeeds($activesOnly=false,$idsOnly=false) {
			$sql;
			if($idsOnly){
				$sql = "SELECT feed.id ";
			} else {
				$sql = "SELECT feed.id, feed.name,feed.is_comment, feed.last_update, feed.protocol, feed.last_fetched, links.url ";
			}
			if($activesOnly){
				$sql .= " FROM ".$this->feedTable." AS feed 
						LEFT JOIN ".$this->feedLinks." AS links ON feed.id = links.feed_id 
						WHERE feed.active='yes' AND links.is_the_one_in_use = 'yes' ";
			} else {
				$sql .= " FROM ".$this->feedTable." AS feed 
						LEFT JOIN ".$this->feedLinks." AS links ON feed.id = links.feed_id 
						WHERE links.is_the_one_in_use = 'yes' ";
			}
			$feeds = array();
			$myrows = $this->wpdb->get_results($sql, ARRAY_A);
			foreach ($myrows as $feed) {
				if(!$idsOnly){
					// if required add option
					$options = $this->wpdb->get_results("SELECT name, value FROM ".$this->feedOptions." WHERE feed_id = '".$feed["id"]."'", ARRAY_A);
					foreach ($options as $option) {
						$feed[$option["name"]] = $option["value"];
					}
				}
				array_push($feeds,$feed);
			}
			return $feeds;
		}
		
		// get category original link
		public function get_blog_link($cat_id){
			$post = get_posts('numberposts=1&category='.(int)$cat_id);
			$post_id = $post[0]->ID;
			$feed_id = get_post_meta($post_id,WP_ARCHIVEPRESS_PREFIX."feed_id", true);
			return $this->wpdb->get_var($this->wpdb->prepare("SELECT url FROM ".$this->feedTable." WHERE id = %d", (int)$feed_id));
		}
		
		// get blog numbers
		public function getBlogs(){
			$blogs = array();
			$blogs["total"] = $this->wpdb->get_var($this->wpdb->prepare("SELECT COUNT(id) FROM ".$this->feedTable." WHERE is_comment = %s", "no"));
			$blogs["active"] = $this->wpdb->get_var($this->wpdb->prepare("SELECT COUNT(id) FROM ".$this->feedTable." WHERE is_comment = %s AND active= %s", "no","yes"));
			return $blogs;
		}
		
		// get post number
		public function getPosts(){
			return $this->wpdb->get_var($this->wpdb->prepare("SELECT COUNT(p.ID) FROM ".$this->wpdb->posts." AS p LEFT JOIN ".$this->wpdb->postmeta ." AS m ON p.ID = m.post_id WHERE p.post_type = %s AND m.meta_key LIKE %s", "post",WP_ARCHIVEPRESS_PREFIX."feed_guid"));
		}
		
		// get fetched comments
		public function getComments(){
			return $this->wpdb->get_var($this->wpdb->prepare("SELECT COUNT(c.comment_ID) FROM ".$this->wpdb->comments." AS c LEFT JOIN ".$this->wpdb->prefix."commentmeta AS m ON c.comment_ID = m.comment_id WHERE  m.meta_key LIKE %s", WP_ARCHIVEPRESS_PREFIX."feed_guid"));
		}
		
		// get authors
		public function getAuthors(){
			return $this->wpdb->get_var($this->wpdb->prepare("SELECT COUNT(u.ID) FROM ".$this->wpdb->users." AS u LEFT JOIN ".$this->wpdb->usermeta ." AS m ON u.ID = m.user_id WHERE  m.meta_key LIKE %s", WP_ARCHIVEPRESS_PREFIX."ori_username"));
		}
		
		// get last fetched
		public function getLastFetched($type="blog"){
			$is_comment = "no";
			if($type == "comment")
				$is_comment = "yes";
			$date = array();
			$feeds = $this->wpdb->get_results("SELECT name, last_update FROM ".$this->feedTable." WHERE is_comment='".$is_comment."' ORDER BY last_update DESC LIMIT 1", ARRAY_A);
			foreach ($feeds as $feed) {
				$date["blog"] = $feed["name"];
				$date["datetime"] = $feed["last_update"];
			}
			return $date;
		}
		
		// get next to fetch
		public function getNextToFetch($type="blog"){
			$is_comment = "no";
			if($type == "comment")
				$is_comment = "yes";
			$date = array();
			$date["datetime"] = 999999999999999999;
			$feeds = $this->wpdb->get_results("SELECT f.name, f.last_update,o.value FROM ".$this->feedTable." AS f LEFT JOIN ".$this->feedOptions." AS o ON f.id = o.feed_id WHERE f.is_comment='".$is_comment."' AND o.name='interval'", ARRAY_A);
			foreach ($feeds as $feed) {
				
				if( (strtotime($feed["last_update"])+(int)$feed["value"]) <  $date["datetime"]){
					$date["blog"] = $feed["name"];
					$date["datetime"] = (strtotime($feed["last_update"])+$feed["value"]);
				}
			}
			return $date;			
		}
		
		// make something "WP nice"
		private function makeNice($elem){
			$elem = sanitize_title($elem);
			$elem = sanitize_user($elem,false);
			return $elem;
		}		
		
		// get wp format dates from a pubDate
		private function getDates($date,$prot){
			$WPdates = array();
			if($prot == ArchivePressOptions::FEED_PROTOCOL_RSS){
				if($date == ""){
					$date = date("D, d M Y H:i:s T");
				}
				$WPdates["date"]	= date("Y-m-d H:i:s",strtotime($date));
				$WPdates["gmt"]		= date("Y-m-d H:i:s",strtotime($date));
			} else {
				if($date == ""){
					$date = date("d M Y H:i:s");
				}
				$WPdates["date"]	= date("Y-m-d H:i:s",strtotime($date));
				$WPdates["gmt"]		= date("Y-m-d H:i:s",strtotime($date));
			}
			return $WPdates;
		}
		
		// get a unique email for a new user
		private function getNewMail() {
			$user_info = array();
			// admin email
			$user_info = get_userdata(1);
			$tmp = explode("@",$user_info->user_email);
			$now = time();
			$mail = $now."@".$tmp[1];
			return $mail;
		}
		
		// delete a post and everything related to it
		private function deletePost($post_id = 0){
			// delete media (delete files from the upload folder)
			// a. GET media
			$wud = wp_upload_dir();
			$upload_path = $wud["basedir"];
			$myrows = $this->wpdb->get_results("SELECT meta_value FROM ".$this->wpdb->postmeta." WHERE meta_key like '%attached_file' and post_id = '".(int)$post_id."' ", ARRAY_A );
			if($myrows) {
				foreach($myrows as $row){
					// b. DELETE media
					unlink($upload_path."/".$row["meta_value"]);
				}
			}
			// delete attachment and post (plus their meta)
			$myrows = $this->wpdb->get_results("SELECT meta_value FROM ".$this->wpdb->postmeta." WHERE meta_key = '".WP_ARCHIVEPRESS_PREFIX."attached_post_id' and post_id = '".(int)$post_id."' ", ARRAY_A );
			if($myrows) {
				foreach($myrows as $row){
					// a. DELETE post
					wp_delete_post( (int)$row["meta_value"], true );
					// b. DELETE attachment
					wp_delete_attachment( (int)$post_id, true );
				}
			}
		
		}
		
		// bring user saved options inside the class (override default settings with the user's one)
		private function refreshClassOptions() {
			// do it only if the plugin has been activated at least one time
			$version = get_option(WP_ARCHIVEPRESS_PREFIX . "version");
			if($version != ""){
				$this->options->version				= get_option(WP_ARCHIVEPRESS_PREFIX . "version");
				$this->options->isRunning			= get_option(WP_ARCHIVEPRESS_PREFIX . "isRunning");
				$this->options->feedsTableName		= get_option(WP_ARCHIVEPRESS_PREFIX . "feedsTableName");
				$this->options->feedLinksTableName	= get_option(WP_ARCHIVEPRESS_PREFIX . "feedLinksTableName");
				$this->options->feedMetaTableName	= get_option(WP_ARCHIVEPRESS_PREFIX . "feedMetaTableName");
				$this->options->feedOptionsTableName= get_option(WP_ARCHIVEPRESS_PREFIX . "feedOptionsTableName");
				$this->options->feedUsersTableName	= get_option(WP_ARCHIVEPRESS_PREFIX . "feedUsersTableName");
				$this->options->logTableName		= get_option(WP_ARCHIVEPRESS_PREFIX . "logTableName");
				$this->options->logTableName		= get_option(WP_ARCHIVEPRESS_PREFIX . "blogs");
				$this->options->logTableName		= get_option(WP_ARCHIVEPRESS_PREFIX . "authors");
				$this->options->logTableName		= get_option(WP_ARCHIVEPRESS_PREFIX . "archives");
				$this->options->logTableName		= get_option(WP_ARCHIVEPRESS_PREFIX . "tags");
				
				// FEED OPTIONS
				$this->options->defFeedProtocol		= get_option(WP_ARCHIVEPRESS_PREFIX . "defFeedProtocol");
				$this->options->defRssVersion		= get_option(WP_ARCHIVEPRESS_PREFIX . "defRssVersion");
				$this->options->defAtomVersion		= get_option(WP_ARCHIVEPRESS_PREFIX . "defAtomVersion");
				$this->options->defFeedFetchInt		= get_option(WP_ARCHIVEPRESS_PREFIX . "defFeedFetchInt");
				$this->options->justAddedIsActive	= get_option(WP_ARCHIVEPRESS_PREFIX . "justAddedIsActive");
				$this->options->showWhatWillDo		= get_option(WP_ARCHIVEPRESS_PREFIX . "showWhatWillDo");
				$this->options->followPermaLink		= get_option(WP_ARCHIVEPRESS_PREFIX . "followPermaLink");
				$this->options->embedMedia			= get_option(WP_ARCHIVEPRESS_PREFIX . "embedMedia");
				$this->options->keepPostAuth		= get_option(WP_ARCHIVEPRESS_PREFIX . "keepPostAuth");
				$this->options->defAuthor			= get_option(WP_ARCHIVEPRESS_PREFIX . "defAuthor");
				$this->options->keepPostCategories	= get_option(WP_ARCHIVEPRESS_PREFIX . "keepPostCategories");
				$this->options->defCategory			= get_option(WP_ARCHIVEPRESS_PREFIX . "defCategory");
				$this->options->tryAutoTag			= get_option(WP_ARCHIVEPRESS_PREFIX . "tryAutoTag");
				$this->options->YahooKey			= get_option(WP_ARCHIVEPRESS_PREFIX . "YahooKey");
				$this->options->useCategoriesAsTags	= get_option(WP_ARCHIVEPRESS_PREFIX . "useCategoriesAsTags");
				$this->options->defPostStatus		= get_option(WP_ARCHIVEPRESS_PREFIX . "defPostStatus");
				$this->options->defCommentsStatus	= get_option(WP_ARCHIVEPRESS_PREFIX . "defCommentsStatus");
				$this->options->postFetchComments	= get_option(WP_ARCHIVEPRESS_PREFIX . "postFetchComments");
				$this->options->tryTypePadStandard	= get_option(WP_ARCHIVEPRESS_PREFIX . "tryTypePadStandard");
				$this->options->areCommentsApproved	= get_option(WP_ARCHIVEPRESS_PREFIX . "areCommentsApproved");
				$this->options->htmlAllowedTags		= get_option(WP_ARCHIVEPRESS_PREFIX . "htmlAllowedTags");
				$this->options->saveContributors	= get_option(WP_ARCHIVEPRESS_PREFIX . "saveContributors");
				$this->options->defContributorLink	= get_option(WP_ARCHIVEPRESS_PREFIX . "defContributorLink");
				$this->options->tryToFindExcerpt	= get_option(WP_ARCHIVEPRESS_PREFIX . "tryToFindExcerpt");
				$this->options->cronType			= get_option(WP_ARCHIVEPRESS_PREFIX . "cronType");
				$this->options->cronKey				= get_option(WP_ARCHIVEPRESS_PREFIX . "cronKey");
				
				// LOG OPTIONS
				$this->options->defLogStatus		= get_option(WP_ARCHIVEPRESS_PREFIX . "defLogStatus");
				$this->options->defLogLevel			= get_option(WP_ARCHIVEPRESS_PREFIX . "defLogLevel");
				
				// PRIVATE OPTIONS
				$this->options->pluginDelIsAllowed	= get_option(WP_ARCHIVEPRESS_PREFIX . "pluginDelIsAllowed");
				$this->options->tryTypePadAttempts	= get_option(WP_ARCHIVEPRESS_PREFIX . "tryTypePadAttempts");
				
				
			}
		}
		
		
		
		// Plugin Activation (also for reActivation after a deactivation or a deletion)
		public function Activate(){
			// check version in wp options to see if this is the first Activation
			$version = get_option(WP_ARCHIVEPRESS_PREFIX . "version");
			if($version == ""){
				// INSTALLATION PROCEDURE
				// 1. add new specific tables
				// a. feeds
				require_once(ABSPATH . 'wp-admin/includes/upgrade.php');
				
				$table_name = $this->feedTable;
   				if($this->wpdb->get_var("SHOW TABLES LIKE '$table_name'") != $table_name) {
   					$sql = "CREATE TABLE " . $table_name . " (
	  						id mediumint(9) NOT NULL AUTO_INCREMENT,
	  						name VARCHAR(50) DEFAULT 'Feed Name' NOT NULL,
							url VARCHAR(200) NOT NULL,
							protocol VARCHAR(5) DEFAULT '".$this->options->defFeedProtocol."' NOT NULL,
							version VARCHAR(8),
							feed_date DATETIME NOT NULL,
							last_update DATETIME NOT NULL,
							is_comment VARCHAR(3) DEFAULT 'no' NOT NULL,
							active VARCHAR(3) DEFAULT 'yes' NOT NULL,
							last_fetched VARCHAR(200),
							UNIQUE KEY id (id)
							);";
					dbDelta($sql);
   				} else {
   					throw new Exception('Table' . $table_name . ' already exists');
   					exit;
   				}
				
				// b. feeds links (will help to prevent feed duplication)
				$table_name = $this->feedLinks;
			   	if($this->wpdb->get_var("SHOW TABLES LIKE '$table_name'") != $table_name) {
   					$sql = "CREATE TABLE " . $table_name . " (
	  						id mediumint(9) NOT NULL AUTO_INCREMENT,
							feed_id mediumint(9) NOT NULL,
	  						url VARCHAR(200) NOT NULL,
							is_the_one_in_use VARCHAR(3) DEFAULT 'no' NOT NULL,
							UNIQUE KEY id (id)
							);";
					dbDelta($sql);   				
			   	} else {
   					throw new Exception('Table' . $table_name . ' already exists');
   					exit;
   				}
   				
   				// c. feed options
				$table_name = $this->feedOptions;
			   	if($this->wpdb->get_var("SHOW TABLES LIKE '$table_name'") != $table_name) {
   					$sql = "CREATE TABLE " . $table_name . " (
	  						id mediumint(9) NOT NULL AUTO_INCREMENT,
							feed_id mediumint(9) NOT NULL,
	  						name VARCHAR(200) NOT NULL,
							value TEXT,
							UNIQUE KEY id (id)
							);";
					dbDelta($sql);   				
			   	} else {
   					throw new Exception('Table' . $table_name . ' already exists');
   					exit;
   				}   				
   				// d. feed meta
				$table_name = $this->feedMeta;
			   	if($this->wpdb->get_var("SHOW TABLES LIKE '$table_name'") != $table_name) {
   					$sql = "CREATE TABLE " . $table_name . " (
	  						id mediumint(9) NOT NULL AUTO_INCREMENT,
							feed_id mediumint(9) NOT NULL,
							value TEXT,
							meta_date DATETIME NOT NULL,
							UNIQUE KEY id (id)
							);";
					dbDelta($sql);   				
			   	} else {
   					throw new Exception('Table' . $table_name . ' already exists');
   					exit;
   				}
			   	// e. feed users: NOW IN wp_usermeta
			   	/*
					$table_name = $this->feedUsers;
				   	if($this->wpdb->get_var("SHOW TABLES LIKE '$table_name'") != $table_name) {
	   					$sql = "CREATE TABLE " . $table_name . " (
		  						id mediumint(9) NOT NULL AUTO_INCREMENT,
								feed_id mediumint(9) NOT NULL,
		  						ori_username VARCHAR(200) NOT NULL,
								add_post_id mediumint(9) NOT NULL,
								add_date DATETIME NOT NULL,
								UNIQUE KEY id (id)
								);";
						dbDelta($sql);   				
				   	} else {
	   					throw new Exception('Table' . $table_name . ' already exists');
	   					exit;
	   				} 
   				*/  				
   				// f. log
				$table_name = $this->logTable;
			   	if($this->wpdb->get_var("SHOW TABLES LIKE '$table_name'") != $table_name) {
   					$sql = "CREATE TABLE " . $table_name . " (
	  						id mediumint(9) NOT NULL AUTO_INCREMENT,
	  						log_date DATETIME NOT NULL,
	  						level VARCHAR(5) NOT NULL,
							message TEXT,
							UNIQUE KEY id (id)
							);";
					dbDelta($sql);   				
			   	} else {
   					throw new Exception('Table' . $table_name . ' already exists');
   					exit;
   				}
   				
				// 2. add wp options
				// PLUGIN OPTIONS
				add_option(WP_ARCHIVEPRESS_PREFIX . "version",				$this->options->pluginVersion);
				add_option(WP_ARCHIVEPRESS_PREFIX . "isRunning", "yes");
				add_option(WP_ARCHIVEPRESS_PREFIX . "feedsTableName",		$this->options->feedsTableName);
				add_option(WP_ARCHIVEPRESS_PREFIX . "feedLinksTableName",	$this->options->feedLinksTableName);
				add_option(WP_ARCHIVEPRESS_PREFIX . "feedMetaTableName",	$this->options->feedMetaTableName);
				add_option(WP_ARCHIVEPRESS_PREFIX . "feedOptionsTableName",	$this->options->feedOptionsTableName);
				add_option(WP_ARCHIVEPRESS_PREFIX . "feedUsersTableName",	$this->options->feedUsersTableName);
				add_option(WP_ARCHIVEPRESS_PREFIX . "logTableName",			$this->options->logTableName);
				add_option(WP_ARCHIVEPRESS_PREFIX . "cronType",				$this->options->cronType);
				add_option(WP_ARCHIVEPRESS_PREFIX . "cronKey",				urlencode(wp_generate_password( 16, false )));
				
				// FEED OPTIONS
				add_option(WP_ARCHIVEPRESS_PREFIX . "defFeedProtocol",		$this->options->defFeedProtocol);
				add_option(WP_ARCHIVEPRESS_PREFIX . "defRssVersion",		$this->options->defRssVersion);
				add_option(WP_ARCHIVEPRESS_PREFIX . "defAtomVersion",		$this->options->defAtomVersion);
				add_option(WP_ARCHIVEPRESS_PREFIX . "defFeedFetchInt",		$this->options->defFeedFetchInt);
				add_option(WP_ARCHIVEPRESS_PREFIX . "justAddedIsActive",	$this->options->justAddedIsActive);
				add_option(WP_ARCHIVEPRESS_PREFIX . "showWhatWillDo",		$this->options->showWhatWillDo);
				add_option(WP_ARCHIVEPRESS_PREFIX . "followPermaLink",		$this->options->followPermaLink);
				add_option(WP_ARCHIVEPRESS_PREFIX . "embedMedia",			$this->options->embedMedia);
				add_option(WP_ARCHIVEPRESS_PREFIX . "keepPostAuth",			$this->options->keepPostAuth);
				add_option(WP_ARCHIVEPRESS_PREFIX . "defAuthor",			$this->options->defAuthor);
				add_option(WP_ARCHIVEPRESS_PREFIX . "keepPostCategories",	$this->options->keepPostCategories);
				add_option(WP_ARCHIVEPRESS_PREFIX . "defCategory",			$this->options->defCategory);
				add_option(WP_ARCHIVEPRESS_PREFIX . "tryAutoTag",			$this->options->tryAutoTag);
				add_option(WP_ARCHIVEPRESS_PREFIX . "YahooKey",				$this->options->YahooKey);
				add_option(WP_ARCHIVEPRESS_PREFIX . "useCategoriesAsTags",	$this->options->useCategoriesAsTags);
				add_option(WP_ARCHIVEPRESS_PREFIX . "defPostStatus",		$this->options->defPostStatus);
				add_option(WP_ARCHIVEPRESS_PREFIX . "defCommentsStatus",	$this->options->defCommentsStatus);
				add_option(WP_ARCHIVEPRESS_PREFIX . "postFetchComments",	$this->options->postFetchComments);
				add_option(WP_ARCHIVEPRESS_PREFIX . "tryTypePadStandard",	$this->options->tryTypePadStandard);
				add_option(WP_ARCHIVEPRESS_PREFIX . "areCommentsApproved",	$this->options->areCommentsApproved);
				add_option(WP_ARCHIVEPRESS_PREFIX . "htmlAllowedTags",		$this->options->htmlAllowedTags);
				add_option(WP_ARCHIVEPRESS_PREFIX . "saveContributors",		$this->options->saveContributors);
				add_option(WP_ARCHIVEPRESS_PREFIX . "defContributorLink",	$this->options->defContributorLink);
				add_option(WP_ARCHIVEPRESS_PREFIX . "tryToFindExcerpt",		$this->options->tryToFindExcerpt);
				
				// LOG OPTIONS
				add_option(WP_ARCHIVEPRESS_PREFIX . "defLogStatus",			$this->options->defLogStatus);
				add_option(WP_ARCHIVEPRESS_PREFIX . "defLogLevel",			$this->options->defLogLevel);
				
				// PRIVATE OPTIONS
				add_option(WP_ARCHIVEPRESS_PREFIX . "pluginDelIsAllowed",	$this->options->pluginDelIsAllowed);
				add_option(WP_ARCHIVEPRESS_PREFIX . "tryTypePadAttempts",	$this->options->tryTypePadAttempts);
				
						
				// pages (for templating)
				$newPost = array();
				$newPost["post_status"]		= "publish"; 
				$newPost["post_type"]		= "page";
				$newPost["comment_status"] 	= "close";
				$newPost["post_author"] 	= 1;
				$newPost["post_content"] 	= "";
				$newPost["post_excerpt"]	= "";
				$newPost["post_title"] 		= __("Browse by blog",ARCHIVEPRESS);
				$newPost["post_name"] 		= "blogs";
				$post_id = wp_insert_post( $newPost );
				update_post_meta($post_id, "_wp_page_template", "categories.php");
				add_option(WP_ARCHIVEPRESS_PREFIX . "blogs",$post_id);
				
				$newPost = array();
				$newPost["post_status"]		= "publish"; 
				$newPost["post_type"]		= "page";
				$newPost["comment_status"] 	= "close";
				$newPost["post_author"] 	= 1;
				$newPost["post_content"] 	= "";
				$newPost["post_excerpt"]	= "";
				$newPost["post_title"] 		= __("Browse by author",ARCHIVEPRESS);
				$newPost["post_name"] 		= "authors";
				$post_id = wp_insert_post( $newPost );
				update_post_meta($post_id, "_wp_page_template", "authors.php");
				add_option(WP_ARCHIVEPRESS_PREFIX . "authors",$post_id);
				
				$newPost = array();
				$newPost["post_status"]		= "publish"; 
				$newPost["post_type"]		= "page";
				$newPost["comment_status"] 	= "close";
				$newPost["post_author"] 	= 1;
				$newPost["post_content"] 	= "";
				$newPost["post_excerpt"]	= "";
				$newPost["post_title"] 		= __("Browse by date",ARCHIVEPRESS);
				$newPost["post_name"] 		= "archives";
				$post_id = wp_insert_post( $newPost );
				update_post_meta($post_id, "_wp_page_template", "archives.php");
				add_option(WP_ARCHIVEPRESS_PREFIX . "archives",$post_id);
				
				$newPost = array();
				$newPost["post_status"]		= "publish"; 
				$newPost["post_type"]		= "page";
				$newPost["comment_status"] 	= "close";
				$newPost["post_author"] 	= 1;
				$newPost["post_content"] 	= "";
				$newPost["post_excerpt"]	= "";
				$newPost["post_title"] 		= __("Browse by tag",ARCHIVEPRESS);
				$newPost["post_name"] 		= "tags";
				$post_id = wp_insert_post( $newPost );
				update_post_meta($post_id, "_wp_page_template", "tags.php");
				add_option(WP_ARCHIVEPRESS_PREFIX . "tags",$post_id);
   	
			} else{
				// the plugin was already installed: check if this is an update
				if((int)str_replace(".","",$version) < $this->options->pluginVersion) {
					// UPDATE PROCEDURE
					update_option(WP_ARCHIVEPRESS_PREFIX . "version", 		$this->options->pluginVersion);
				}
				update_option(WP_ARCHIVEPRESS_PREFIX . "isRunning", "yes");
				
				// bring user saved options inside the class (override default settings with the user's one)
				$this->refreshClassOptions();
			}
			
		}
		// Plugin Deactivation
		public function Deactivate(){
			// STOP cron tab jobs
			update_option(WP_ARCHIVEPRESS_PREFIX . "isRunning", "no");
		}	
		// Plugin deletion
		public function Remove(){
			if($this->options->pluginDelIsAllowed == ArchivePressOption::YES){
				// get last user options (useful to get table names and other settings)
				$this->refreshClassOptions();
				
				// delete everything related to the plugin
				// OPTIONS
				delete_option(WP_ARCHIVEPRESS_PREFIX . "version");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "isRunning");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "feedsTableName");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "feedLinksTableName");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "feedMetaTableName");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "feedOptionsTableName");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "feedUsersTableName");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "logTableName");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "blogs");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "authors");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "archives");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "tags");
				
				// FEED OPTIONS
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defFeedProtocol");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defRssVersion");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defAtomVersion");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defFeedFetchInt");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "justAddedIsActive");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "showWhatWillDo");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "followPermaLink");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "embedMedia");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "keepPostAuth");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defAuthor");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "keepPostCategories");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defCategory");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "tryAutoTag");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "YahooKey");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "useCategoriesAsTags");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defPostStatus");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defCommentsStatus");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "postFetchComments");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "tryTypePadStandard");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "areCommentsApproved");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "htmlAllowedTags");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "saveContributors");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defContributorLink");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "tryToFindExcerpt");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "cronType");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "cronKey");
				
				// LOG OPTIONS
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defLogStatus");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "defLogLevel");
				
				// PRIVATE OPTIONS
				delete_option(WP_ARCHIVEPRESS_PREFIX . "pluginDelIsAllowed");
				delete_option(WP_ARCHIVEPRESS_PREFIX . "tryTypePadAttempts");
				
				
				// POSTS, POST METADATA AND AUTHORS
				// 1. find archivePress posts
				$myrows = $this->wpdb->get_results("SELECT post_id FROM ".$this->wpdb->postmeta." WHERE meta_key = '".WP_ARCHIVEPRESS_PREFIX."ori_media_link' GROUP BY post_id ", ARRAY_A );
				if($myrows) {
					foreach($myrows as $row){
						// 2. delete post and everything related
						$this->deletePost($row["post_id"]);
					}
				}
				
				// 3. post authors
				$myrows = $this->wpdb->get_results("SELECT user_id FROM ".$this->wpdb->usermeta." WHERE meta_key = '".WP_ARCHIVEPRESS_PREFIX."ori_username' GROUP BY user_id ", ARRAY_A );
				if($myrows) {
					foreach($myrows as $row){
						wp_delete_user( $row["user_id"] );
					}
				}
				
				// TABLES
				$this->wpdb->query("DROP TABLE ".$this->feedTable."");
				$this->wpdb->query("DROP TABLE ".$this->feedLinks."");
				$this->wpdb->query("DROP TABLE ".$this->feedOptions."");
				$this->wpdb->query("DROP TABLE ".$this->feedMeta."");
				$this->wpdb->query("DROP TABLE ".$this->feedUsers."");
				$this->wpdb->query("DROP TABLE ".$this->logTable."");
				
				// IMPORTANT: right now categories, tags and contributors ARE NOT DELETED
			}
			// otherwise the user will just remove the plugin files, 
			// but nothing is lost!
		}	
		
	}
?>